﻿// Original author contact info: Owen Emlen (owene_1998@yahoo.com)
// Note: other individuals may also have contributed to this code
// Project hosted on CodePlex.com as of 1/10/2009 at http://www.codeplex.com/EmlenMud
using System.Text;
using System.Runtime.Serialization;
using System;
using System.Threading;
using System.ComponentModel;
using System.Collections;
using System.Collections.Generic;
using BrainTechLLC.ThreadSafeObjects;
using WordsMatching;
using System.Xml.Serialization;
using System.Collections.Specialized;
#if USE_HYPER
using Hyper.ComponentModel;
#endif

namespace BrainTechLLC
{
    [Serializable]
    [DataContract]
#if NO_SILVERLIGHT
    //[TypeDescriptionProvider(typeof(HyperTypeDescriptionProvider))]
#endif
    public class BaseAssociatedId : BasePropertyChangeSupport, IAssociatedID
    {
        [DataMember]
        public long _associatedID;

        [NonSerialized, XmlIgnore]
        public bool _isRegistered;

        [XmlIgnore]
        public long AssociatedID
        {
            get { return _associatedID; }
            set
            {
                if (!_associatedID.AreEqual(value))
                {
                    OnPropertyChanging("AssociatedID", _associatedID, value);
                    _associatedID = value;
                    OnPropertyChanged("AssociatedID", _associatedID, value);
                }
            }
        }

        [Category("World")]
#if NO_SILVERLIGHT
        [EditorBrowsable(EditorBrowsableState.Always)]
#endif
        [XmlIgnore]
        public bool IsRegistered
        {
            get { return _isRegistered; }
            set
            {
                if (!_isRegistered.AreEqual(value))
                {
                    OnPropertyChanging("IsRegistered", _isRegistered, value);
                    _isRegistered = value;
                    OnPropertyChanged("IsRegistered", _isRegistered, value);
                }
            }
        }

        public virtual void Register()
        {
            long oldValue = AssociatedID;

            if (AssociatedID == 0)
            {
                oldValue = Interlocked.CompareExchange(ref _associatedID, Everything.CreateUniqueId(), 0);

                if (oldValue == 0)
                {
                    _isRegistered = true;
                    Everything.Register(this);
                }
            }
            else
            {
                lock (this)
                {
                    if (!_isRegistered)
                    {
                        _isRegistered = true;
                        Everything.Register(this);
                    }
                }
            }
        }        
    }
}